package org.deng.learn.lambda;

import java.util.function.*;

/**
 * @author 邓力宾
 * @date 2020/12/17 14:39
 * @desc
 */
public class LambdaDemo {

    public static void main(String[] args) {
/*        m1();
        m2(new Function<Integer, Integer>() {
            @Override
            public Integer apply(Integer integer) {
                return integer + 1;
            }
        });
        //简写
        m2(i-> i + 1);

        m3(i-> System.out.println(i));
        //简写成方法引用
        m3(System.out::println);

        m4();
        m5();
        m6();*/
        m7();

    }

    /**
     * lambda写法
     */
    public static void m1(){
        // Java8之前的写法
        Teacher t = new Teacher() {
            @Override
            public String teach() {
                return "数学";
            }
        };
        System.out.println(t.teach());

        // java8 lambda写法
        t = ()->"语文";
        System.out.println(t.teach());
    }

    /**
     * 使用jdk提供的函数接口
     * Function<Integer,Integer> :　函数接口　一个输入，返回值 都为Integer类型
     */
    public static void m2(Function<Integer,Integer> function){
        System.out.println(function.apply(1));
    }

    /**
     * 使用jdk提供的函数接口
     * Consumer<Integer> 函数接口　一个输入，为Integer类型 没有返回
     * @param consumer
     */
    public static void m3(Consumer<Integer> consumer){
        consumer.accept(100);
    }

    /**
     * 静态方法引用
     */
    public static void m4(){
        //完整写法
        Function<Integer, Integer> f = new Function<Integer, Integer>() {
            @Override
            public Integer apply(Integer integer) {
                return Adder.add(integer);
            }
        };
        //简写
        f = i -> Adder.add(i);

        //继续简写
        f = Adder::add;
        System.out.println(f.apply(10));

        //当输入参数和返回值类型一致时
        UnaryOperator<Integer> u  = Adder::add;
        System.out.println(u.apply(12));

        //当输入参数和返回值类型一致且为Integer类型时
        IntUnaryOperator iu = Adder::add;
        System.out.println(iu.applyAsInt(13));
    }

    /**
     * 实例方法引用
     */
    public static void m5(){
        Adder a = new Adder();
        //完整写法两个输入参数，返回为Integer(实例方法，第一个参数为this指针，只是被省略掉了)
        BiFunction<Adder, Integer, Integer> bi = new BiFunction<Adder, Integer, Integer>() {
            @Override
            public Integer apply(Adder adder, Integer integer) {
                return adder.add2(integer);
            }
        };
        //简写成lambda
        bi = (adder, i)->adder.add2(i);
        System.out.println(bi.apply(a, 10));
        //简写成方法引用,类似静态方法，只是使用时传入具体的实例
        bi = Adder::add2;
        System.out.println(bi.apply(a, 111));

    }

    /**
     * 构造方法引用
     */
    public static void m6(){
        //无参构造方法, 没有参数返回值为实例类型
        //完整写法
        Supplier<Adder> supplier = new Supplier<Adder>() {
            @Override
            public Adder get() {
                return new Adder();
            }
        };
        //使用方法引用
        supplier = Adder::new;
        System.out.println(supplier.get().add2(2));

        //有参构造方法 输入参数为boolean类型，返回为实例类型
        Function<Boolean, Adder> f = Adder::new;
        Adder adder = f.apply(true);
        System.out.println(adder.add2(23));
    }

    /**
     * 级联
     */
    public static void m7(){

        //完整写法
        Function<Integer, Function<Integer, Integer>> f2 = new Function<Integer, Function<Integer, Integer>>() {
            @Override
            public Function<Integer, Integer> apply(Integer i) {
                return new Function<Integer, Integer>() {
                    @Override
                    public Integer apply(Integer j) {
                        return i + j;
                    }
                };
            };
        };
        System.out.println(f2.apply(3).apply(4));
        //简写
         f2 = i->{return j->i+j;};
         //继续简写
        f2 = i->j->i+j;
        System.out.println(f2.apply(3).apply(4));


    }

}
